package com.clarence.dada.modular.system.dict.service.impl;

import cn.hutool.core.convert.Convert;
import cn.hutool.core.lang.TypeReference;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.clarence.dada.core.auth.context.LoginContext;
import com.clarence.dada.core.base.PageResult;
import com.clarence.dada.core.enums.ErrorEnum;
import com.clarence.dada.core.enums.YesOrNotEnum;
import com.clarence.dada.core.exception.BusException;
import com.clarence.dada.core.factory.PageFactory;
import com.clarence.dada.core.factory.PageResultFactory;
import com.clarence.dada.modular.system.dict.entity.SysDictTypeEntity;
import com.clarence.dada.modular.system.dict.entity.req.DictTypeReq;
import com.clarence.dada.modular.system.dict.entity.resp.SysDictTypeResp;
import com.clarence.dada.modular.system.dict.enums.DictTypeClassEnum;
import com.clarence.dada.modular.system.dict.mapper.DictTypeMapper;
import com.clarence.dada.modular.system.dict.service.DictTypeService;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

/**
 * 字典类型 服务实现类
 *
 * @author GD
 * @since 2020/12/26 22:36
 */
@Service
public class DictTypeServiceImpl extends ServiceImpl<DictTypeMapper, SysDictTypeEntity> implements DictTypeService {

    @Override
    public void dictTypeAdd(DictTypeReq req) {
        // 如果是系统级字典，只允许管理员操作
        validateSystemTypeClassOperate(req);
        this.save(Convert.convert(SysDictTypeEntity.class, req));
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void dictTypeDelete(DictTypeReq req) {
        // 如果是系统级字典，只允许管理员操作
        validateSystemTypeClassOperate(req);

        SysDictTypeEntity sysDictTypeEntity = this.querySysDictType(req);
        sysDictTypeEntity.setDelFlag(YesOrNotEnum.Y.getCode());
        this.updateById(sysDictTypeEntity);

    }

    @Override
    public SysDictTypeResp dictTypeDetail(DictTypeReq req) {
        SysDictTypeEntity sysDictTypeEntity = this.getOne(this.createWrapper(req), false);
        if (ObjectUtil.isNotEmpty(sysDictTypeEntity)) {
            return Convert.convert(new TypeReference<>() {}, sysDictTypeEntity);
        } else {
            return new SysDictTypeResp();
        }
    }

    @Override
    public PageResult<SysDictTypeResp> dictTypePage(DictTypeReq req) {
        Page<SysDictTypeEntity> page = this.page(PageFactory.defaultPage(), this.createWrapper(req));
        List<SysDictTypeResp> respList = Convert.convert(new TypeReference<>() {}, page.getRecords());
        return PageResultFactory.result(page, respList);
    }


    /**
     * 校验dictTypeClass是否是系统字典，如果是系统字典只能超级管理员操作
     *
     * @author GD
     * @since 2020/12/25 15:57
     */
    private void validateSystemTypeClassOperate(DictTypeReq req) {
        if (DictTypeClassEnum.SYSTEM_TYPE.getCode().equals(req.getDictTypeClass()) && (!LoginContext.me().getSuperAdminFlag())) {
            throw new BusException(ErrorEnum.SYSTEM_DICT_NOT_ALLOW_OPERATION);
        }
    }

    /**
     * 根据主键id获取对象
     *
     * @author GD
     * @since 2021/1/26 13:28
     */
    private SysDictTypeEntity querySysDictType(DictTypeReq req) {
        SysDictTypeEntity sysDictTypeEntity = this.getById(req.getDictTypeId());
        if (ObjectUtil.isEmpty(sysDictTypeEntity)) {
            throw new BusException(ErrorEnum.DICT_TYPE_NOT_EXISTED);
        }
        return sysDictTypeEntity;
    }

    /**
     * 实体构建queryWrapper
     *
     * @author GD
     * @since 2021/1/24 22:03
     */
    private LambdaQueryWrapper<SysDictTypeEntity> createWrapper(DictTypeReq req) {
        LambdaQueryWrapper<SysDictTypeEntity> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(ObjectUtil.isNotEmpty(req.getDictTypeId()), SysDictTypeEntity::getDictTypeId, req.getDictTypeId())
                .eq(StrUtil.isNotBlank(req.getDictTypeCode()), SysDictTypeEntity::getDictTypeCode, req.getDictTypeCode())
                .like(StrUtil.isNotBlank(req.getDictTypeName()), SysDictTypeEntity::getDictTypeName, req.getDictTypeName())
                .eq(SysDictTypeEntity::getDelFlag, YesOrNotEnum.N.getCode());
        return queryWrapper;
    }

}
